package com.cet.designapplication.service;

import com.cet.designapplication.dutychain.AbstractBusinessHandler;
import com.cet.designapplication.dutychain.CityHandler;
import com.cet.designapplication.dutychain.builder.BusinessHandlerEnum;
import com.cet.designapplication.pojo.BusinessLaunch;
import com.cet.designapplication.pojo.UserInfo;
import com.cet.designapplication.repo.BusinessLaunchRepository;
import com.cet.designapplication.repo.UserRepository;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;

import java.util.Arrays;
import java.util.Date;
import java.util.List;

/**
 * @author NSOC
 */

@Service
public class UserService {

    @Autowired
    private UserRepository userRepository;

    @Autowired
    private BusinessLaunchRepository businessLaunchRepository;

    @Value("${duty.chain}")
    private String handlerType;

    private String currentHandlerType;

    // 业务投放责任链头结点
    private AbstractBusinessHandler currentHandler;

    public String login(String account, String password) {
        UserInfo userInfo = userRepository.findByUserNameAndUserPassword(account, password);

        if (userInfo == null) {
            return "account / password ERROR!";
        }
        return "login success!";
    }

    public String register(UserInfo userInfo) {
        if (checkUserExists(userInfo.getUserName())) {
            throw new RuntimeException("User already registered!");
        }
        userInfo.setCreateDate(new Date());
        userRepository.save(userInfo);
        return "Register success!";
    }

    protected boolean checkUserExists(String userName) {
        UserInfo user = userRepository.findByUserName(userName);
        return user != null;
    }

    public List<BusinessLaunch> filterBusinessLaunch(String city, String sex, String product) {
        List<BusinessLaunch> launchList = businessLaunchRepository.findAll();
        return buildChain().processHandler(launchList, city, sex, product);
    }

    private AbstractBusinessHandler buildChain() {
        if (handlerType == null) {
            throw new RuntimeException("未配置责任链");
        }

        if (currentHandlerType == null) {
            this.currentHandlerType = handlerType;
        }

        if (handlerType.equals(currentHandlerType) && currentHandler != null) {
            return currentHandler;
        } else {
            System.out.println("首次初始化或duty.chain配置改变，重新组装责任链！");
            synchronized (this) {
                try {
                    AbstractBusinessHandler dummyHandler = new CityHandler();
                    AbstractBusinessHandler preHandler = dummyHandler;
                    String[] handlerTypeList = handlerType.split(",");
                    for (String handlerType : handlerTypeList) {
                        AbstractBusinessHandler businessHandler = (AbstractBusinessHandler) Class.forName(BusinessHandlerEnum.valueOf(handlerType).getValue()).newInstance();
                        preHandler.nextHandler = businessHandler;
                        preHandler = businessHandler;
                    }
                    currentHandler = dummyHandler.nextHandler;
                    currentHandlerType = handlerType;
                    return  currentHandler;
                } catch (Exception e) {
                    throw new UnsupportedOperationException(e);
                }
            }
        }
    }


}
